package com.xiaolin.renju.kernel;

import java.io.*;
import java.util.Objects;
import java.util.UUID;

/**
 * @author zhengjin.liu
 * @since 2021/12/2 17:02
 */
public class RenJuKernel {

    private String id;

    private Long updateTime;

    private final Process process;

    private final BufferedWriter writer;

    private final BufferedReader reader;

    private String oldUserPlace;

    private String oldAiPlace;

    private final static long TIMEOUT_MATCH = 600000L;

    private Long timeoutTurn = 1000L;

    public RenJuKernel() {
        try {
            this.process = Runtime.getRuntime().exec(System.getProperty("user.dir") + "/ai/ai.exe");
            this.writer = new BufferedWriter(new OutputStreamWriter(this.process.getOutputStream()));
            reader = new BufferedReader(new InputStreamReader(this.process.getInputStream()));
        } catch (IOException e) {
            e.printStackTrace();
            throw new RuntimeException(e.getMessage());
        }
    }

    public void beat() {
        updateTime = System.currentTimeMillis();
    }

    public String start() {
        if (this.id != null) {
            send("RESTART");
        } else {
            send("START 19");
            this.id = UUID.randomUUID().toString().replaceAll("-", "");
        }
        final String message = getMessage();
        if (!"OK".equals(message)) {
            throw new RuntimeException("棋盘创建异常！");
        }
        send(String.format("INFO timeout_match %s", TIMEOUT_MATCH));
        send(String.format("INFO timeout_turn %s", timeoutTurn));
        return this.id;
    }

    public String begin() {
        send("BEGIN");
        oldAiPlace = getMessage();
        return oldAiPlace;
    }

    public String turn(Integer y, Integer x) {
        send(String.format("TURN %s,%s", y, x));
        oldUserPlace = String.format("%s,%s", y, x);
        oldAiPlace = getMessage();
        return oldAiPlace;
    }

    public boolean takeBack() {
        if (Objects.isNull(oldAiPlace) || Objects.isNull(oldUserPlace)) {
            return false;
        }
        send(String.format("TAKEBACK %s", oldAiPlace));
        oldAiPlace = null;
        getMessage();
        send(String.format("TAKEBACK %s", oldUserPlace));
        oldUserPlace = null;
        getMessage();
        return true;
    }

    private void send(String message) {
        try {
            System.out.println("通知AI：" + message);
            writer.write(message);
            writer.newLine();
            writer.flush();
            updateTime = System.currentTimeMillis();
        } catch (IOException e) {
            e.printStackTrace();
            throw new RuntimeException(e.getMessage());
        }
    }

    private String getMessage() {
        try {
            String line;
            while ((line = reader.readLine()) != null) {
                if (line.length() == 0 || line.startsWith("MESSAGE") || line.startsWith("DEBUG")) {
                    continue;
                }
                System.out.println("AI回复：" + line);
                break;
            }
            updateTime = System.currentTimeMillis();
            return line;
        } catch (IOException e) {
            e.printStackTrace();
            throw new RuntimeException(e.getMessage());
        }
    }

    public void setTimeoutTurn(Long timeoutTurn) {
        this.timeoutTurn = timeoutTurn;
    }

    public boolean isOvertime() {
        return System.currentTimeMillis() - updateTime > 60000;
    }

    public String getId() {
        return id;
    }

    public void destroy() {
        try {
            process.destroy();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}
